package com.authine.cloudpivot.web.api.controller;

import com.alibaba.fastjson.JSONObject;
import com.authine.cloudpivot.engine.enums.ErrCode;
import com.authine.cloudpivot.web.api.controller.base.BaseController;
import com.authine.cloudpivot.web.api.dao.ControlPharmacyMapper;
import com.authine.cloudpivot.web.api.view.ResponseResult;
import com.authine.cloudpivot.web.api.vo.ControlPharmacy;
import com.authine.cloudpivot.web.enums.ControlPharmacyEnum;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.ss.usermodel.*;
import org.mybatis.spring.MyBatisSystemException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Objects;

/**
 * @ClassName QueryRuntimeExtController
 * @Description: 模拟云枢系统，实现定制化的导入功能
 * @Author fj
 * @Date 2021/1/24
 * @Version V1.0
 **/
@Api(value = "扩展接口", tags = "运行时::列表查询接口")
@RestController
@RequestMapping("/public/query")
@Slf4j
public class QueryRuntimeExtController extends BaseController {
    @Autowired
    private ControlPharmacyMapper controlPharmacyMapper;
    @ApiOperation(value = "列表文件上传")
    @PostMapping("/importFile")
    @Transactional
    public ResponseResult<Void> importFile(MultipartFile excelFile) {
        try {
            // 获取文件全称，根据文件后缀判断文件格式
            String originalFilename = excelFile.getOriginalFilename();
            if (!originalFilename.matches("^.+\\.(?i)(xls)$") && !originalFilename.matches("^.+\\.(?i)(xlsx)$")) {
                log.error("上传文件格式不正确，请上传excel文件");
                return getErrResponseResult(ErrCode.DATABASE_ILLEGAL.getErrCode(), "上传文件格式不正确，请上传excel文件");
            }
            List<ControlPharmacy> controlPharmacyList = new ArrayList<>();
            JSONObject headerJson = new JSONObject();
            JSONObject controlPharmacyJson = null;
            // 获取文件的输入流
            InputStream inputStream = excelFile.getInputStream();
            // 创建Workbook对象
            Workbook wb = WorkbookFactory.create(inputStream);
            // 获取excel中的第一个表单
            Sheet firstSheet = wb.getSheetAt(0);
            // 读取excel第一行的header信息
            Row headerRow = firstSheet.getRow(1);
            // 获取所有头信息
            Iterator<Cell> cellIterator = headerRow.cellIterator();
            while (cellIterator.hasNext()) {
                Cell headerCell = cellIterator.next();
                if (ControlPharmacyEnum.get(headerCell.getStringCellValue()) != null) {
                    // 将所有头信息放到headerJson里面
                    headerJson.put(ControlPharmacyEnum.get(headerCell.getStringCellValue()).getChineseName(),
                            ControlPharmacyEnum.get(headerCell.getStringCellValue()).getEnglishName());
                }
            }
            log.info("-----------headerJson：{}-----------",headerJson.toJSONString());
            Row dataRow = null;
            Cell dataCell = null;
            ControlPharmacy controlPharmacy = null;
            // 获取所有数据行
            for (int i = 2; i < firstSheet.getPhysicalNumberOfRows(); i++) {
                dataRow = firstSheet.getRow(i);
                controlPharmacyJson = new JSONObject();
                // 获取所有数据列
                for (int j = 0; j < dataRow.getPhysicalNumberOfCells(); j++) {
                    dataCell = dataRow.getCell(j);
                    if (dataCell != null) {
                        // 如果header中存在此key，添加到数据信息里面
                        if (headerJson.getString(headerRow.getCell(j).getStringCellValue()) != null) {
                            controlPharmacyJson.put(headerJson.getString(headerRow.getCell(j).getStringCellValue()), getStringCellValue(dataCell));
                        }
                    }
                }
                controlPharmacy = JSONObject.parseObject(controlPharmacyJson.toJSONString(), ControlPharmacy.class);
                log.info("-----------controlPharmacy：{}-----------",JSONObject.toJSONString(controlPharmacy));
                controlPharmacyList.add(controlPharmacy);
            }
            // 数据更新，根据id更新药品管控信息
            if (controlPharmacyList.size() > 0) {
                String objectId = "";
                for (int i = 0; i < controlPharmacyList.size(); i ++) {
                    try {
                        objectId = controlPharmacyList.get(i).getId();
                        if (!StringUtils.isEmpty(objectId)) {
                            controlPharmacyMapper.updateControlPharmacySelective(controlPharmacyList.get(i));
                        } else {
                            return getErrResponseResult(ErrCode.UNKNOW_ERROR.getErrCode(), "数据导入失败，导出文件时请勾选'业务对象ID'，然后重新导入。");
                        }
                    } catch (Exception e) {
                        log.error(e.getMessage());
                        return getErrResponseResult(ErrCode.UNKNOW_ERROR.getErrCode(), "网络不给力，请稍后再试");
                    }
                }
            }
        } catch (IOException e) {
            log.error(e.getMessage());
            e.printStackTrace();
            return getErrResponseResult(ErrCode.UNKNOW_ERROR.getErrCode(), "网络不给力，请稍后再试");
        }
        return getOkResponseResult("数据导入成功");
    }

    /**
     * 将单元格的值转换成字符串
     * @param cell
     * @return
     */
    private static String getStringCellValue(Cell cell) {
        String strCell = null;
        switch (cell.getCellType()) {
            case NUMERIC:
                if (DateUtil.isCellDateFormatted(cell)) {
                    strCell = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(cell.getDateCellValue());
                } else {
                    DecimalFormat df = new DecimalFormat("0.######");
                    boolean isPercent = cell.getCellStyle().getDataFormatString().contains("%");
                    if (isPercent) {//假如是百分数
                        if (Objects.nonNull(cell.getNumericCellValue())) {
                            BigDecimal decimal = new BigDecimal(cell.getNumericCellValue());
                            decimal = decimal.multiply(new BigDecimal(100));
                            strCell = df.format(decimal);
                        }
                    } else {
                        strCell = String.valueOf(df.format(cell.getNumericCellValue()));
                    }
                    if (StringUtils.isEmpty(strCell) || "null".equals(strCell)) {
                        strCell = null;
                    }
                }
                break;
            case STRING:
                strCell = cell.getStringCellValue();
                break;
            case FORMULA:
                strCell = cell.getCellFormula();
                break;
            case BLANK:
                strCell = null;
                break;
            case BOOLEAN:
                strCell = String.valueOf(cell.getBooleanCellValue());
                break;
            case ERROR:
                strCell = null;
                break;
            default:
                throw new IllegalArgumentException("Invalid cell type " + cell.getCellType());
        }
        if ("".equals(strCell)) {
            strCell = null;
        }
        return strCell;
    }
}
